package utils;

import domain.Payload;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.Jws;
import io.jsonwebtoken.Jwts;

import java.security.PrivateKey;
import java.security.PublicKey;
import java.util.Base64;
import java.util.UUID;

import io.jsonwebtoken.SignatureAlgorithm;
import org.joda.time.DateTime;
public class JwtUtils {
    private static final String JWT_PAYLOAD_USER_KEY = "user";
/**
 * 私钥加密token
 *
 * @param userInfo   载荷中的数据
 * @param privateKey 私钥
 * @param expire     过期时间，单位分钟
 * @return JWT
 */
 public static String generateTokenExpireInMinutes(Object userInfo, PrivateKey privateKey,int expire){
      return Jwts.builder()
              .claim(JWT_PAYLOAD_USER_KEY,JsonUtils.toString(userInfo))
              .setId(createJTI())
              .setExpiration(DateTime.now().plusMinutes(expire).toDate())
              .signWith(privateKey, SignatureAlgorithm.RS256)
              .compact();
 }
    /**
     * 公钥解析token
     *
     * @param token     用户请求中的token
     * @param publicKey 公钥
     * @return Jws<Claims>
     */
    private static Jws<Claims> parserToken(String token, PublicKey publicKey){
        return Jwts.parser().setSigningKey(publicKey).parseClaimsJws(token);
    }

    private static String createJTI(){
        return  new String(Base64.getEncoder().encode(UUID.randomUUID().toString().getBytes()));
    }

    /**
     * 获取token中的用户信息
     *
     * @param token     用户请求中的令牌
     * @param publicKey 公钥
     * @return 用户信息
     */
    private static <T> Payload<T> getInfoFromToken(String token,PublicKey publicKey,Class<T> userType){
        Jws<Claims> claimsJws = parserToken(token,publicKey);
        Claims body = claimsJws.getBody();
        Payload<T> calims = new Payload<>();
        calims.setId(body.getId());
        calims.setExpiration(body.getExpiration());
        return  calims;
    }

    /**
     * 获取token中的载荷信息
     *
     * @param token     用户请求中的令牌
     * @param publicKey 公钥
     * @return 用户信息
     */
    public static <T> Payload<T> getInfoFromToken(String token, PublicKey publicKey) {
        Jws<Claims> claimsJws = parserToken(token, publicKey);
        Claims body = claimsJws.getBody();
        Payload<T> claims = new Payload<>();
        claims.setId(body.getId());
        claims.setExpiration(body.getExpiration());
        return claims;
    }
}
